From 80d9a6abdd76cf7b4f206326264966e91f936115 Mon Sep 17 00:00:00 2001 From: Keir Fraser Date: Mon, 11 Oct 2010 09:01:45 +0100 Subject: [PATCH] x86: emulate MSR_IA32_UCODE_REV Intel access protocol Intel requires a write of zeros (hence such writes now get silently ignored) followed by a cpuid(1) followed by the actual read. Includes some code redundancy elimination possible after the actual change. Signed-off-by: Jan Beulich --- xen/arch/x86/traps.c | 27 ++++++++++++++++++++------- 1 file changed, 20 insertions(+), 7 deletions(-) diff --git a/xen/arch/x86/traps.c b/xen/arch/x86/traps.c index c1f480fdb5..e811f6257c 100644 --- a/xen/arch/x86/traps.c +++ b/xen/arch/x86/traps.c @@ -2276,6 +2276,14 @@ static int emulate_privileged_op(struct cpu_user_regs *regs) if ( wrmsr_safe(MSR_FAM10H_MMIO_CONF_BASE, msr_content) != 0 ) goto fail; break; + case MSR_IA32_UCODE_REV: + if ( boot_cpu_data.x86_vendor != X86_VENDOR_INTEL ) + goto fail; + if ( rdmsr_safe(regs->ecx, val) ) + goto fail; + if ( msr_content ) + goto invalid; + break; case MSR_IA32_MISC_ENABLE: if ( rdmsr_safe(regs->ecx, val) ) goto invalid; @@ -2382,11 +2390,16 @@ static int emulate_privileged_op(struct cpu_user_regs *regs) regs->eax = regs->edx = 0; break; } - if ( rdmsr_safe(regs->ecx, msr_content) != 0 ) - goto fail; - regs->eax = (uint32_t)msr_content; - regs->edx = (uint32_t)(msr_content >> 32); - break; + goto rdmsr_normal; + case MSR_IA32_UCODE_REV: + BUILD_BUG_ON(MSR_IA32_UCODE_REV != MSR_AMD_PATCHLEVEL); + if ( boot_cpu_data.x86_vendor == X86_VENDOR_INTEL ) + { + if ( wrmsr_safe(MSR_IA32_UCODE_REV, 0) ) + goto fail; + sync_core(); + } + goto rdmsr_normal; case MSR_IA32_MISC_ENABLE: if ( rdmsr_safe(regs->ecx, msr_content) ) goto fail; @@ -2394,8 +2407,6 @@ static int emulate_privileged_op(struct cpu_user_regs *regs) regs->eax = (uint32_t)msr_content; regs->edx = (uint32_t)(msr_content >> 32); break; - case MSR_EFER: - case MSR_AMD_PATCHLEVEL: default: if ( rdmsr_hypervisor_regs(regs->ecx, &val) ) { @@ -2411,6 +2422,8 @@ static int emulate_privileged_op(struct cpu_user_regs *regs) if ( rc ) goto rdmsr_writeback; + case MSR_EFER: + rdmsr_normal: /* Everyone can read the MSR space. */ /* gdprintk(XENLOG_WARNING,"Domain attempted RDMSR %p.\n", _p(regs->ecx));*/ -- 2.30.2